package com.lib.common.adapter;

import android.content.Context;
import android.util.Log;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;

import androidx.annotation.NonNull;
import androidx.recyclerview.widget.RecyclerView;

import com.lib.common.R;
import com.lib.utils.XLog;

import java.util.LinkedList;
import java.util.List;

/**
 * @author 一叶丶枫凌
 * Last Modify on 2020-06-25
 */
public abstract class BaseRecyclerAdapter<DATA> extends RecyclerView.Adapter<BaseRecyclerAdapter.BaseViewHolder<DATA>> {
    private final List<DATA> mDataList = new LinkedList<>();

    protected Context mContext;
    protected View.OnClickListener mL;
    protected View.OnLongClickListener mLCL;

    public BaseRecyclerAdapter(Context context) {
        mContext = context;
    }

    @Override
    final public int getItemViewType(int position) {
        DATA data = getData(position);
        if (data instanceof BaseViewHolder.BaseData) {
            return ((BaseViewHolder.BaseData) data).getItemViewType();
        }
        return position;
    }

    @Override
    final public long getItemId(int position) {
        DATA data = getData(position);
        if (data instanceof BaseViewHolder.BaseData) {
            return ((BaseViewHolder.BaseData) data).getItemId();
        }
        return position;
    }

    @Override
    final public int getItemCount() {
        return mDataList.size();
    }

    @NonNull
    @Override
    final public BaseViewHolder<DATA> onCreateViewHolder(@NonNull ViewGroup parent, int viewType) {
        try {
            BaseViewHolder<DATA> baseViewHolder = initView(parent, viewType);
            return baseViewHolder;
        } catch (Throwable e) {
            XLog.w("catch info->" + Log.getStackTraceString(e));
//            继承BaseViewHolder的子类必须是静态类或者独立类
//            如果这里异常了，可以换成对应的ViewHolder进行测试
//            baseViewHolder = new ViewHolder(view, mContext, this);
            View view = LayoutInflater.from(mContext).inflate(R.layout.jmsg_view_holder_unkown, parent, false);
            UnknownViewHolder<DATA> holder = new UnknownViewHolder<>(view);
            return holder;
        }
    }

    @Override
    final public void onBindViewHolder(@NonNull BaseViewHolder holder, int position) {
        position = holder.getAdapterPosition();
        DATA data = getData(position);
        boolean onBind = onBindViewHolder(holder, data, position);
        if (!onBind) {
            holder.onBindViewHolder(data, position);
        }
    }

    public boolean onBindViewHolder(BaseViewHolder<DATA> holder, DATA data, int position) {
        return false;
    }

    final protected View getViewByLayoutResId(ViewGroup rootView, int layoutResId) {
        return LayoutInflater.from(mContext).inflate(layoutResId, rootView, false);
    }

    protected abstract BaseViewHolder<DATA> initView(ViewGroup parent, int viewType);

    final public boolean setData(List<DATA> list) {
        if (list == null || list.size() == 0) {
            return false;
        }
        mDataList.clear();
        mDataList.addAll(list);
        notifyDataSetChanged();
        return true;
    }

    final public void addData(DATA data) {
        if (data == null) {
            return;
        }
        int position = mDataList.size();
        mDataList.add(data);
        notifyItemInserted(position);
        notifyItemRangeChanged(position, mDataList.size());
    }

    final public void addData(List<DATA> list) {
        if (list == null || list.size() == 0) {
            return;
        }
        int start = mDataList.size();
        mDataList.addAll(list);
        int size = mDataList.size();
        notifyItemRangeInserted(start, size);
        notifyItemRangeChanged(start, size);
    }

    final public void removeData(int position) {
        int size = mDataList.size();
        if (size == 0) {
            return;
        }
        mDataList.remove(position);
        notifyItemRemoved(position);
        notifyItemRangeChanged(position, size);
    }

    final public void clear() {
        mDataList.clear();
        notifyDataSetChanged();
    }

    final public List<DATA> getData() {
        return mDataList;
    }

    final public DATA getData(int adapterPosition) {
        DATA baseData = null;
        try {
            baseData = mDataList.get(adapterPosition);
        } catch (Exception e) {
            e.printStackTrace();
        }
        return baseData;
    }

    public void toDestroy() {
        mDataList.clear();
        mContext = null;
        mL = null;
    }

    public void setOnClickListener(View.OnClickListener l) {
        mL = l;
    }

    public View.OnClickListener getOnClickListener() {
        return mL;
    }

    public View.OnLongClickListener getOnLongClickListener() {
        return mLCL;
    }

    public void setOnLongClickListener(View.OnLongClickListener LCL) {
        mLCL = LCL;
    }

    public static abstract class BaseViewHolder<DATA> extends RecyclerView.ViewHolder {
        public BaseViewHolder(View view) {
            super(view);
        }

        public void onBindViewHolder(DATA data, int position) {
        }

        public interface BaseData {
            int getItemViewType();

            long getItemId();
        }
    }

    public static class UnknownViewHolder<DATA> extends BaseViewHolder<DATA> {
        public UnknownViewHolder(View view) {
            super(view);
        }

        @Override
        public void onBindViewHolder(DATA data, int position) {

        }
    }
}